package com.shiro.demo.project.system.login.services;

import com.shiro.demo.project.system.login.domain.Permission;
import com.shiro.demo.project.system.login.domain.Role;
import com.shiro.demo.project.system.login.domain.User;
import com.shiro.demo.project.system.login.mappers.UserMapper;
import lombok.NonNull;
import org.apache.shiro.crypto.SecureRandomNumberGenerator;
import org.apache.shiro.crypto.hash.Md5Hash;
import org.apache.shiro.util.ByteSource;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;

import java.util.Arrays;

@Service
public class AccountServiceImpl implements IAccountService {
    @Autowired
    UserMapper userMapper;

    @Transactional
    @Override
    public void register(@NonNull User user) {
        Assert.hasText(user.getPassword(), "密码不能为空");

        ByteSource salt = new SecureRandomNumberGenerator().nextBytes(8);
        user.setSalt(salt.toHex());
        Md5Hash md5Hash = new Md5Hash(user.getPassword(), user.getSalt(), 5);
        user.setPassword(md5Hash.toHex());

        Assert.isTrue(userMapper.insertUser(user) == 1, "插入用户失败");
        if(user.getRoles() == null){
            Role role = new Role(user.getUsername(),"guest");
            user.setRoles(Arrays.asList(role));
        }

        user.getRoles().forEach(role -> {
            Assert.isTrue( userMapper.insertRole(role) == 1, "插入角色失败");

            if(role.getPermissions() == null) {
                Permission permission = new Permission("read");
                permission.setRoleName(role.getRoleName());
                role.setPermissions(Arrays.asList(permission));
            }

            role.getPermissions().forEach(permission -> {
                Assert.isTrue(userMapper.insertPermission(permission) == 1, "插入权限失败");
            });
        });

    }

    @Override
    public int countOfUserName(String userName) {
        return userMapper.countOfUserName(userName);
    }
}
